package com.star.common.email;

import com.star.common.email.config.EmailProperties;
import com.star.common.email.factory.EmailFactory;
import com.star.common.email.service.StarEmailService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.BeanFactory;
import org.springframework.beans.factory.BeanFactoryAware;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.config.BeanPostProcessor;
import org.springframework.beans.factory.support.BeanDefinitionBuilder;
import org.springframework.beans.factory.support.BeanDefinitionRegistry;
import org.springframework.beans.factory.support.GenericBeanDefinition;
import org.springframework.mail.javamail.JavaMailSender;
import org.springframework.stereotype.Component;

import java.util.Map;

/**
 * bean的后置处理器加锁对象，采用aop方式
 *
 * @author zhouhengzhe
 */
@Slf4j
@Component
public class StarEmailBeanPostProcessor extends EmailFactory implements BeanPostProcessor, BeanFactoryAware {
    private BeanFactory beanFactory;

    @Autowired
    private Map<String, EmailProperties> emailPropertiesMap;

    @Override
    public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
        if (Initialized.allowInit(emailPropertiesMap)) {
            for (Map.Entry<String, EmailProperties> entry : emailPropertiesMap.entrySet()) {
                String emailName = "email" + ":" + entry.getKey();
                BeanDefinitionRegistry registry = (BeanDefinitionRegistry) beanFactory;
                JavaMailSender javaMailSender = javaMailSender(entry.getValue());
                registerCzEmailSender(registry, emailName, javaMailSender,entry.getValue());
            }
        }
        return BeanPostProcessor.super.postProcessAfterInitialization(bean, beanName);
    }

    private void registerCzEmailSender(BeanDefinitionRegistry registry,
                                       String emailName,
                                       JavaMailSender javaMailSender,
                                       EmailProperties emailProperties) {
        BeanDefinitionBuilder definitionBuilder = BeanDefinitionBuilder.genericBeanDefinition(StarEmailService.class);
        GenericBeanDefinition genericBeanDefinition = (GenericBeanDefinition) definitionBuilder.getBeanDefinition();
        genericBeanDefinition.getConstructorArgumentValues().addIndexedArgumentValue(0, javaMailSender);
        genericBeanDefinition.getConstructorArgumentValues().addIndexedArgumentValue(1, emailProperties);
        registry.registerBeanDefinition(emailName,genericBeanDefinition);
        log.info("init register`emailName=" + emailName);
    }

    @Override
    public void setBeanFactory(BeanFactory beanFactory) throws BeansException {
        this.beanFactory = beanFactory;
    }
}
